package com.jwsoft.manager.core.integration.impl;

import cn.hutool.core.convert.Convert;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.bifang.engine.assistant.core.annotation.ApiService;
import com.bifang.engine.assistant.core.annotation.OpApi;
import com.bifang.engine.assistant.core.annotation.SaveOplog;
import com.bifang.engine.assistant.core.enums.AuTypeEnum;
import com.bifang.engine.assistant.core.enums.AuthStatusEnum;
import com.bifang.engine.assistant.core.enums.BoolEnum;
import com.bifang.engine.assistant.core.enums.FuncTypeEnum;
import com.bifang.engine.assistant.core.exception.AppException;
import com.bifang.engine.assistant.core.utils.SessionUtil;
import com.bifang.engine.data.core.util.PagerUtil;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.jwsoft.manager.common.enums.EnrollBackTypeEnum;
import com.jwsoft.manager.common.enums.EnrollStatusFormalEnum;
import com.jwsoft.manager.common.enums.SchoolCategoryEnum;
import com.jwsoft.manager.common.vo.eduEnrollBack.EduEnrollBackAuditVO;
import com.jwsoft.manager.common.vo.eduEnrollBack.EduEnrollBackKeyVO;
import com.jwsoft.manager.common.vo.eduEnrollBack.EduEnrollBackQueryVO;
import com.jwsoft.manager.common.vo.eduEnrollBack.EduEnrollBackVO;
import com.jwsoft.manager.common.vo.eduStudentEnroll.EduStudentEnrollKeyVO;
import com.jwsoft.manager.common.vo.eduStudentEnroll.EduStudentEnrollVO;
import com.jwsoft.manager.common.vo.eduStudentEnroll.UpdateEnrollStatusVO;
import com.jwsoft.manager.common.vo.eduStudentEnrollKindergarten.EduStudentEnrollKindergartenKeyVO;
import com.jwsoft.manager.core.dao.model.EduEnrollBack;
import com.jwsoft.manager.core.dao.model.EduSchool;
import com.jwsoft.manager.core.dao.model.EduStudentEnrollPre;
import com.jwsoft.manager.core.dao.service.EduEnrollBackService;
import com.jwsoft.manager.core.dao.service.EduSchoolService;
import com.jwsoft.manager.core.dao.service.EduStudentEnrollPreService;
import com.jwsoft.manager.core.integration.EduEnrollBackIntegration;
import com.jwsoft.manager.core.integration.EduStudentEnrollIntegration;
import com.jwsoft.manager.core.integration.EduStudentEnrollKindergartenIntegration;
import com.jwsoft.manager.core.util.EduEnrollClearCacheHelper;
import com.jwsoft.manager.core.util.EduHelper;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import org.springframework.util.ObjectUtils;

import java.util.Date;
import java.util.List;

/**
 * 退回审核管理业务实现类
 *
 * @author hhj
 * @since 2023-04-04
 */
@ApiService(funcCode = "enrollBack", title = "退回审核管理")
public class EduEnrollBackIntegrationImpl implements EduEnrollBackIntegration {

    @Autowired
    public EduEnrollBackService eduEnrollBackService;

    @Autowired
    private EduSchoolService eduSchoolService;

    @Autowired
    private EduStudentEnrollKindergartenIntegration eduStudentEnrollKindergartenIntegration;

    @Autowired
    private EduStudentEnrollIntegration eduStudentEnrollIntegration;
    @Autowired
    private EduStudentEnrollPreService eduStudentEnrollPreService;

    @Autowired
    private EduEnrollClearCacheHelper eduEnrollClearCacheHelper;
    @Autowired
    private EduHelper eduHelper;

    @Override
    @OpApi(funcCode = "enrollBack0001", title = "退回审核管理分页查询", funcType = FuncTypeEnum.query)
    public PageInfo<EduEnrollBackVO> getList(EduEnrollBackQueryVO vo) {
        // 开启分页
        if (vo.getPageNum() == null || vo.getPageSize() == null) {
            //如果不传入分页参数，默认最大取1000条
            vo.setPageNum(1);
            vo.setPageSize(1000);
        }
        PageHelper.startPage(vo.getPageNum(), vo.getPageSize());
        QueryWrapper<EduEnrollBack> enrollBackQueryWrapper = new QueryWrapper<>();
        enrollBackQueryWrapper.lambda()
                .eq(!ObjectUtils.isEmpty(vo.getYear()),
                        EduEnrollBack::getYear,
                        vo.getYear())
                .eq(!ObjectUtils.isEmpty(vo.getEnrollBackType()),
                        EduEnrollBack::getEnrollBackType,
                        vo.getEnrollBackType())
                .eq(!ObjectUtils.isEmpty(vo.getFullName()),
                        EduEnrollBack::getFullName,
                        vo.getFullName())
                .eq(!ObjectUtils.isEmpty(vo.getIdcard()),
                        EduEnrollBack::getIdcard,
                        vo.getIdcard())
                .eq(!ObjectUtils.isEmpty(vo.getSchoolId()),
                        EduEnrollBack::getSchoolId,
                        vo.getSchoolId())
                .eq(!ObjectUtils.isEmpty(vo.getSchoolAuthStatus()),
                        EduEnrollBack::getSchoolAuthStatus,
                        vo.getSchoolAuthStatus())
                .eq(!ObjectUtils.isEmpty(vo.getAuthStatus()),
                        EduEnrollBack::getAuthStatus,
                        vo.getAuthStatus())
                .eq(!ObjectUtils.isEmpty(vo.getAreaCode()),
                        EduEnrollBack::getAreaCode,
                        vo.getAreaCode());
        List<EduEnrollBack> list = eduEnrollBackService.list(enrollBackQueryWrapper);
        if (CollectionUtils.isEmpty(list)) {
            // 判断是否为空，为空则返回空参数
            return PagerUtil.createEmptyPagerInfo(vo.getPageNum(), vo.getPageSize());
        }
        // 不为空则获取分页结果
        PageInfo<EduEnrollBack> pageInfo = new PageInfo<>(list);
        // 返回参数需要通过common层的vo实体类，用该方法可以批量转换
        List<EduEnrollBackVO> resultList = Convert.toList(EduEnrollBackVO.class, pageInfo.getList());

        // 转义数据字典值
        // dictHelper.valueToName(resultList, Arrays.asList(DemoDictEnum.values()));
        return PagerUtil.parsePagerVo(resultList, pageInfo);
    }

    @Override
    @OpApi(funcCode = "enrollBack0002", title = "退回审核管理根据主键查询详情", funcType = FuncTypeEnum.query)
    public EduEnrollBackVO getById(EduEnrollBackKeyVO vo) {
        EduEnrollBack entity = eduEnrollBackService.getById(vo.getEduEnrollBackId());
        if (ObjectUtils.isEmpty(entity)) {
            throw new AppException("查询不到详细信息!");
        }
        EduEnrollBackVO result = Convert.convert(EduEnrollBackVO.class, entity);
        return result;
    }

    /**
     * 保存前统一校验
     */
    @Override
    @OpApi(funcCode = "enrollBack0003", title = "退回审核管理保存前校验", funcType = FuncTypeEnum.other, checkPrivilege = BoolEnum.FALSE)
    public void checkSave(EduEnrollBackVO vo) {
        //主键为空为新增校验

        //主键不为空为修改校验
    }

    @Override
    @OpApi(funcCode = "enrollBack0004", title = "退回审核管理新增", funcType = FuncTypeEnum.insert)
    @SaveOplog(
            operationType = "enrollBack0004",
            operationName = "退回审核管理新增",
            dataType = "eduEnrollBackId",
            auType = AuTypeEnum.OTHER)
    @Transactional
    public EduEnrollBackVO add(EduEnrollBackVO vo) {
        //保存前校验
        checkSave(vo);
        //保存数据
        EduEnrollBack entity = Convert.convert(EduEnrollBack.class, vo);
        eduEnrollBackService.save(entity);
        //将主键设置回vo使操作日志可以取到
        vo.setEduEnrollBackId(entity.getEduEnrollBackId());
        clearCache(entity.getIdcard());
        return vo;
    }

    @Override
    @OpApi(funcCode = "enrollBack0005", title = "退回审核管理修改", funcType = FuncTypeEnum.update)
    @SaveOplog(
            operationType = "enrollBack0005",
            operationName = "退回审核管理修改",
            dataType = "eduEnrollBackId",
            auType = AuTypeEnum.OTHER)
    @Transactional
    public EduEnrollBackVO edit(EduEnrollBackVO vo) {
        if (ObjectUtils.isEmpty(vo.getEduEnrollBackId())) {
            throw new AppException("传入需要修改的主键不能为空!");
        }
        EduEnrollBack oldEntity = eduEnrollBackService.getById(vo.getEduEnrollBackId());
        if (ObjectUtils.isEmpty(oldEntity)) {
            throw new AppException("查询不到需要修改的信息!");
        }
        //保存前校验
        checkSave(vo);
        //保存数据
        EduEnrollBack entity = Convert.convert(EduEnrollBack.class, vo);
        eduEnrollBackService.updateById(entity);
        clearCache(entity.getIdcard());
        return vo;
    }

    @Override
    @OpApi(funcCode = "enrollBack0006", title = "退回审核管理根据主键删除", funcType = FuncTypeEnum.delete)
    @SaveOplog(
            operationType = "enrollBack0006",
            operationName = "退回审核管理删除",
            dataType = "eduEnrollBackId",
            auType = AuTypeEnum.OTHER)
    @Transactional
    public void del(EduEnrollBackKeyVO vo) {
        if (ObjectUtils.isEmpty(vo.getEduEnrollBackId())) {
            throw new AppException("传入需要删除的数据主键不能为空!");
        }
        EduEnrollBack entity = eduEnrollBackService.getById(vo.getEduEnrollBackId());
        if (ObjectUtils.isEmpty(entity)) {
            throw new AppException("未找到需要删除的信息!");
        }
        eduEnrollBackService.removeById(vo.getEduEnrollBackId());
        clearCache(entity.getIdcard());
    }

    @Override
    @OpApi(funcCode = "enrollBack0007", title = "学校退回/退出信息审核", funcType = FuncTypeEnum.update)
    @SaveOplog(
            operationType = "enrollBack0007",
            operationName = "学校退回/退出信息审核",
            dataType = "eduEnrollBackId",
            auType = AuTypeEnum.OTHER)
    @Transactional
    public void backAuditEnrollBack(EduEnrollBackAuditVO vo) {
        Long id = vo.getEduEnrollBackId();
        EduEnrollBack eduEnrollBack = eduEnrollBackService.getById(id);
        String schoolId = eduEnrollBack.getSchoolId();
        if (eduEnrollBack == null) {
            throw new AppException("待审核的数据不存在");
        }
        if (!AuthStatusEnum.NODO.getType().equalsIgnoreCase(eduEnrollBack.getBackStatus())) {
            throw new AppException("该业务已退回报名完成，不能重复操作");
        }
        // 更新审核状态
        eduEnrollBack.setSchoolAuthStatus(vo.getAuthStatus());
        eduEnrollBack.setSchoolAuthRemarks(vo.getAuthRemarks());
        eduEnrollBack.setSchoolAuthTime(new Date());
        eduEnrollBack.setSchoolAuthUserId(SessionUtil.getUserId());
        //更新退回状态
        if(EnrollBackTypeEnum.BACK.getType().equalsIgnoreCase(eduEnrollBack.getEnrollBackType())){
            eduEnrollBack.setBackStatus(eduEnrollBack.getSchoolAuthStatus());
        }else {
            eduEnrollBack.setBackStatus(eduEnrollBack.getAuthStatus());
        }

        eduEnrollBackService.updateById(eduEnrollBack);

        EduSchool eduSchool = eduSchoolService.getById(schoolId);
        if ((!ObjectUtils.isEmpty(eduSchool)) && AuthStatusEnum.YES.getType().equalsIgnoreCase(eduEnrollBack.getBackStatus())) {
            if (EnrollBackTypeEnum.BACK.getType().equalsIgnoreCase(eduEnrollBack.getEnrollBackType())) {
                if (SchoolCategoryEnum.KINDERGARTEN.getType().equalsIgnoreCase(eduSchool.getSchoolCategory())) {
                    // 幼儿园退回报名
                    EduStudentEnrollKindergartenKeyVO kindergartenKeyVO = new EduStudentEnrollKindergartenKeyVO();
                    kindergartenKeyVO.setFormDetailId(eduEnrollBack.getStudentEnrollId());
                    eduStudentEnrollKindergartenIntegration.nurseryFormBack(kindergartenKeyVO);
                } else {
                    // 义务段退回报名
                    EduStudentEnrollKeyVO eduStudentEnrollKeyVO = new EduStudentEnrollKeyVO();
                    eduStudentEnrollKeyVO.setStudentEnrollId(eduEnrollBack.getStudentEnrollId());
                    eduStudentEnrollIntegration.ywApplyBack(eduStudentEnrollKeyVO);
                }
            } else {
                if (SchoolCategoryEnum.KINDERGARTEN.getType().equalsIgnoreCase(eduSchool.getSchoolCategory())) {
                    // 幼儿园退出报名
                    throw new AppException("无当前操作权限!");
                } else {
                    // 义务段退出报名
                    UpdateEnrollStatusVO eduStudentEnrollVO = new UpdateEnrollStatusVO();
                    eduStudentEnrollVO.setStudentEnrollId(eduEnrollBack.getStudentEnrollId());
                    eduStudentEnrollVO.setEnrollStatus(EnrollStatusFormalEnum.xtblq.getType());
                    eduStudentEnrollIntegration.updateEnrollStatus(eduStudentEnrollVO);
                }
            }
        }
    }

    @Override
    @OpApi(funcCode = "enrollBack0008", title = "录取退出信息审核(管理员)", funcType = FuncTypeEnum.update)
    @SaveOplog(
            operationType = "enrollBack0008",
            operationName = "录取退出信息审核(管理员)",
            dataType = "eduEnrollBackId",
            auType = AuTypeEnum.OTHER)
    @Transactional
    public void returnAuditEnrollBack(EduEnrollBackAuditVO vo) {
        Long id = vo.getEduEnrollBackId();
        EduEnrollBack eduEnrollBack = eduEnrollBackService.getById(id);
        String schoolId = eduEnrollBack.getSchoolId();
        if (eduEnrollBack == null) {
            throw new AppException("待审核的数据不存在");
        }
        if (!AuthStatusEnum.NODO.getType().equalsIgnoreCase(eduEnrollBack.getBackStatus())) {
            throw new AppException("该业务已退出报名完成，不能重复操作");
        }
        // 更新审核状态
        eduEnrollBack.setAuthStatus(vo.getAuthStatus());
        eduEnrollBack.setAuthRemarks(vo.getAuthRemarks());
        eduEnrollBack.setAuthTime(new Date());
        eduEnrollBack.setAuthUserId(SessionUtil.getUserId());
        //更新退回状态
        eduEnrollBack.setBackStatus(eduEnrollBack.getAuthStatus());

        eduEnrollBackService.updateById(eduEnrollBack);

        EduSchool eduSchool = eduSchoolService.getById(schoolId);
        if ((!ObjectUtils.isEmpty(eduSchool)) && AuthStatusEnum.YES.getType().equalsIgnoreCase(eduEnrollBack.getBackStatus())) {
            if (SchoolCategoryEnum.KINDERGARTEN.getType().equalsIgnoreCase(eduSchool.getSchoolCategory())) {
                // 幼儿园退出报名
                throw new AppException("无当前操作权限!");
            } else {
                // 义务段退出报名
                UpdateEnrollStatusVO eduStudentEnrollVO = new UpdateEnrollStatusVO();
                eduStudentEnrollVO.setStudentEnrollId(eduEnrollBack.getStudentEnrollId());
                eduStudentEnrollVO.setEnrollStatus(EnrollStatusFormalEnum.xtblq.getType());
                eduStudentEnrollIntegration.updateEnrollStatus(eduStudentEnrollVO);
            }
        }
    }

    //清除缓存
    private void clearCache(String idcard){
        //查询人员
        if(StringUtils.isBlank(idcard)){
            return;
        }

        QueryWrapper<EduStudentEnrollPre> queryPreWrapper=new QueryWrapper<>();
        queryPreWrapper.lambda().select(EduStudentEnrollPre::getStudentEnrollPreId,EduStudentEnrollPre::getIdcard,EduStudentEnrollPre::getFatherIdcard,EduStudentEnrollPre::getMotherIdcard)
                .eq(EduStudentEnrollPre::getYear,eduHelper.thisYear())
                .and( wrapper -> {
                    wrapper.eq(EduStudentEnrollPre::getIdcard, idcard)
                            .or()
                            .eq(EduStudentEnrollPre::getFatherIdcard, idcard)
                            .or()
                            .eq(EduStudentEnrollPre::getMotherIdcard, idcard);
                });
        List<EduStudentEnrollPre> list=eduStudentEnrollPreService.list(queryPreWrapper);
        if (CollectionUtils.isEmpty(list)){
            return;
        }
        for (EduStudentEnrollPre pre:list) {
            //我的报名
            eduEnrollClearCacheHelper.clearCacheMyEnroll(pre.getFatherIdcard());
            eduEnrollClearCacheHelper.clearCacheMyEnroll(pre.getMotherIdcard());
            eduEnrollClearCacheHelper.clearCacheMyEnroll(pre.getIdcard());
        }
    }
}
